﻿using System.Linq.Expressions;

namespace System.Linq
{
    #region 2表链接
    /// <summary>
    /// 2表链接
    /// </summary>
    public interface IJoinQueryable<T1, T2>
    {
        IQueryable<TResult> Select<TResult>(Expression<Func<T1, T2, TResult>> selectSelector);
        IJoinQueryable<T1, T2> Where(Expression<Func<T1, T2, bool>> predicate);
        IJoinQueryable<T1, T2> OrderBy<TKey>(Expression<Func<T1, T2, TKey>> keySelector, OrderType orderType = OrderType.Asc);
    }

    /// <summary>
    /// 2表链接
    /// </summary>
    public interface IJoinStartQueryable<T1, T2> : IJoinQueryable<T1, T2>
    {
        IJoinStartQueryable<T1, T2, T3> Join<T3>(IQueryable<T3> source, JoinType joinType);
        IJoinStartQueryable<T1, T2> On(Expression<Func<T1, T2, bool>> onPredicate);
    }
    #endregion

    #region 3表链接

    /// <summary>
    /// 3表链接
    /// </summary>
    public interface IJoinQueryable<T1, T2, T3>
    {
        IQueryable<TResult> Select<TResult>(Expression<Func<T1, T2, T3, TResult>> selectSelector);
        IJoinQueryable<T1, T2, T3> Where(Expression<Func<T1, T2, T3, bool>> predicate);

        IJoinQueryable<T1, T2, T3> OrderBy<TKey>(Expression<Func<T1, T2, T3, TKey>> keySelector, OrderType orderType = OrderType.Asc);
    }

    /// <summary>
    /// 3表链接
    /// </summary>
    public interface IJoinStartQueryable<T1, T2, T3> : IJoinQueryable<T1, T2, T3>
    {
        IJoinStartQueryable<T1, T2, T3, T4> Join<T4>(IQueryable<T4> source, JoinType joinType);

        IJoinStartQueryable<T1, T2, T3> On(Expression<Func<T1, T2, T3, bool>> onPredicate);

        IJoinStartQueryable<T1, T2, T3> On(Expression<Func<T2, T3, bool>> onPredicate);
    }
    #endregion

    #region 4表链接
    /// <summary>
    /// 4表链接
    /// </summary>
    public interface IJoinQueryable<T1, T2, T3, T4>
    {
        IQueryable<TResult> Select<TResult>(Expression<Func<T1, T2, T3, T4, TResult>> selectSelector);

        IJoinQueryable<T1, T2, T3, T4> Where(Expression<Func<T1, T2, T3, T4, bool>> predicate);

        IJoinQueryable<T1, T2, T3, T4> OrderBy<TKey>(Expression<Func<T1, T2, T3, T4, TKey>> keySelector, OrderType orderType = OrderType.Asc);
    }

    /// <summary>
    /// 4表链接
    /// </summary>
    public interface IJoinStartQueryable<T1, T2, T3, T4> : IJoinQueryable<T1, T2, T3, T4>
    {
        IJoinStartQueryable<T1, T2, T3, T4, T5> Join<T5>(IQueryable<T5> source, JoinType joinType);

        IJoinStartQueryable<T1, T2, T3, T4> On(Expression<Func<T1, T2, T3, T4, bool>> onPredicate);

        IJoinStartQueryable<T1, T2, T3, T4> On(Expression<Func<T3, T4, bool>> onPredicate);
    }

    #endregion

    #region 5表链接
    /// <summary>
    /// 5表链接为止
    /// </summary>
    public interface IJoinQueryable<T1, T2, T3, T4, T5>
    {
        IQueryable<TResult> Select<TResult>(Expression<Func<T1, T2, T3, T4, T5, TResult>> selectSelector);
        IJoinQueryable<T1, T2, T3, T4, T5> Where(Expression<Func<T1, T2, T3, T4, T5, bool>> predicate);

        IJoinQueryable<T1, T2, T3, T4, T5> OrderBy<TKey>(Expression<Func<T1, T2, T3, T4, T5, TKey>> keySelector, OrderType orderType = OrderType.Asc);
    }

    /// <summary>
    /// 5表链接
    /// </summary> 
    public interface IJoinStartQueryable<T1, T2, T3, T4, T5> : IJoinQueryable<T1, T2, T3, T4, T5>
    {
        IJoinStartQueryable<T1, T2, T3, T4, T5> On(Expression<Func<T1, T2, T3, T4, T5, bool>> onPredicate);

        IJoinStartQueryable<T1, T2, T3, T4, T5> On(Expression<Func<T4, T5, bool>> onPredicate);
    }
    #endregion

}
